Passed
Branchmaster (c7c38d)
by Plamen
01:28
created

table.js ➔ ... ➔ this.init   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
eloc 2
c 1
b 0
f 0
dl 0
loc 3
rs 10
cc 1
nc 1
nop 1
1
var strAsc = String.fromCharCode(9650); //▲
2
var strDesc = String.fromCharCode(9660);//▼
3
var xmlhttp; var d;
4
5
var table = new function(){
6
    this.rq = null;
7
    this.tail = [];
8
    
9
    this.ReloadData = function(tableId){
10
        var request = {};
11
        this.BuildRequest(request,tableId);
12
        this.LoadData(tableId,request);  
13
    }; 
14
    
15
    this.BuildRequest = function(request, crntTableId, skipPropertyArray){
16
        this.rq = request;
17
        this.checkSkip = function(skipProperty){
18
            var result = false;
19
            if(skipPropertyArray && Object.prototype.toString.call( skipPropertyArray ) === '[object Array]'){
20
                if(skipPropertyArray.indexOf(skipProperty)>=0){
21
                    result = true;
22
                }
23
            }
24
            return result;
25
        };
26
        this.getSort = function(){
27
            var table = document.getElementById(crntTableId);
28
            var thTags = table.getElementsByTagName("thead")[0].getElementsByTagName("th");
29
            for(var i = 0; i < thTags.length; i++ ){
30
                if(thTags[i].getElementsByTagName("a")[0] && thTags[i].getElementsByTagName("a")[0].getElementsByTagName("span").length === 1){
31
                    var spanContent = thTags[i].getElementsByTagName("a")[0].getElementsByTagName("span")[0].innerHTML;
32
                    if(spanContent.length === 1){
33
                        this.rq.colNo = i;
34
                        this.rq.colOrd = (spanContent === window.strDesc) ? "desc" : "asc";
35
                    }
36
                }
37
            }
38
        };
39
        this.getFilter = function(){
40
            var r = this.getFilterFieldsByTbaleID(crntTableId);
41
            if(r.filter !== null){
42
                this.rq.filter = r.filter;
43
            }
44
            if(r.filterBy !== null){
45
                this.rq.filterBy = r.filterBy;
46
            }
47
        };
48
49
        /* Build request object */
50
        if(!this.checkSkip("sort")){            this.getSort();         }
51
        if(!this.checkSkip("filter")){          this.getFilter();       }
52
53
        this.rq.tableId = crntTableId;
54
        return this.rq;
55
    };
56
57
    this.RequestToUrl = function(rq){
58
        var url=location.pathname + ".json" + location.search;
59
        if(typeof rq === "object"){
60
            var getUrlVarName = {colNo: "col", colOrd: "ord", filter: "filter", filterBy: "filter-by", pageNo: "pg", exportType: "export", tableId: "table-id"};
61
            var flagFirst = location.search.length < 1 ? true : false;
62
            for(var r in rq){
1 ignored issue
show
Complexity introduced by
A for in loop automatically includes the property of any prototype object, consider checking the key using hasOwnProperty.

When iterating over the keys of an object, this includes not only the keys of the object, but also keys contained in the prototype of that object. It is generally a best practice to check for these keys specifically:

var someObject;
for (var key in someObject) {
    if ( ! someObject.hasOwnProperty(key)) {
        continue; // Skip keys from the prototype.
    }

    doSomethingWith(key);
}
Loading history...
63
                url += (flagFirst===true ? "?" : "&") + getUrlVarName[r] + "=" + rq[r];
64
                flagFirst = false;
65
            }
66
        }
67
        return url;
68
    };
69
70
    this.Filter = function(field){
71
        var request = {};
72
        var isSelect = field.tagName.toLowerCase() === "select";
73
        if(isSelect){
74
            var f = field.parentNode.parentNode.getElementsByTagName("input")[0];
75
            if('' === f.value){
76
                return;
77
            }
78
        }
79
        var crntTableId = isSelect ? 
80
                            f.getAttribute("data-table-id") : 
0 ignored issues
show
Bug introduced by
The variable f does not seem to be initialized in case isSelect on line 73 is false. Are you sure this can never be the case?
Loading history...
81
                            field.getAttribute("data-table-id");
82
        var exRq = this.rq;
83
        this.BuildRequest(request,crntTableId);
84
        if(exRq===null){
85
            this.LoadData(crntTableId,request);
86
        } else if(  request.filter !== exRq.filter || 
87
                    request.filterBy !== exRq.filterBy
88
        ){
89
            this.LoadData(crntTableId,request);
90
        }
91
    };
92
93
    this.GoPage = function(lnk){
94
        var request = {};
95
        var table = this.getParent(lnk,"table");
96
        var crntTableId = table.getAttribute("id");
97
        this.BuildRequest(request,crntTableId);
98
        //check & serve pagination jump links
99
        var jumpDir=lnk.innerHTML.trim().substr(0,1);
100
        if(jumpDir==="+" || jumpDir==="-"){
101
            var current = table.querySelector("tfoot .paging .a").innerHTML;
102
            var jump = lnk.innerHTML.replace("K","000").replace("M","000000000");
103
            var jumpPage = (parseInt(current)+parseInt(jump));
104
            lnk.parentNode.setAttribute("data-page",jumpPage);
105
            lnk.style.transform="none";
106
        }
107
        request.pageNo = lnk.parentNode.hasAttribute("data-page") ?
108
                         lnk.parentNode.getAttribute("data-page") : 
109
                         lnk.innerHTML;
110
        this.LoadData(crntTableId,request);
111
        return false;
112
    };
113
114
    this.Export = function(lnk,eType){
115
        var request = {};
116
        var crntTableId = this.getParent(lnk,"table").getAttribute("id");
117
        this.BuildRequest(request,crntTableId);
118
        request.exportType = ["CSV","Excel"].indexOf(eType)>=0 ? eType : "csv";
119
        window.open(this.RequestToUrl(request));
120
        return false;
121
    };
122
123
    this.Sort = function(colNo,lnk){
124
        var request = {};
125
        var crntTableId = this.getParent(lnk,"table").getAttribute("id");
126
        this.BuildRequest(request,crntTableId);
127
        if(Math.round(colNo) === request.colNo){
128
            request.colOrd = request.colOrd === "asc" ? "desc" : "asc";
129
        } else {
130
            request.colNo=Math.round(colNo);
131
            request.colOrd = "asc";
132
        }
133
        this.LoadData(crntTableId,request);
134
        /* Clear and add new sort arrow */
135
        var headSpans = this.getParent(lnk,"thead").getElementsByTagName("span");
136
        for(var i=0; i < headSpans.length; i++){
137
            headSpans[i].innerHTML = "";
138
        }
139
        lnk.getElementsByTagName("span")[0].innerHTML = (request.colOrd === "desc" ? window.strDesc : window.strAsc);
140
    };
141
    
142
    this.DrawSection = function(tableContainer, dt, tSection){
143
        var section = tSection === "tfoot" ? "tfoot" : "tbody";
144
        tSection =  document.getElementById(tableContainer).
145
                        getElementsByTagName(section)[0];
146
        this.clearSection(tSection);
147
        for(var i=0; i < dt.length; i++) {
148
            var row = dt[i];
149
            var tRow = document.createElement("tr");
150
            for(var cell in row){
1 ignored issue
show
Complexity introduced by
A for in loop automatically includes the property of any prototype object, consider checking the key using hasOwnProperty.

When iterating over the keys of an object, this includes not only the keys of the object, but also keys contained in the prototype of that object. It is generally a best practice to check for these keys specifically:

var someObject;
for (var key in someObject) {
    if ( ! someObject.hasOwnProperty(key)) {
        continue; // Skip keys from the prototype.
    }

    doSomethingWith(key);
}
Loading history...
151
                var tCell = document.createElement("td");
152
                if(typeof row[cell] === "string" || typeof row[cell] === "number"){
153
                    tCell.innerHTML = row[cell];
154
                } else if(typeof row[cell] === "object"){
155
                    for(var attr in row[cell]){
1 ignored issue
show
Complexity introduced by
A for in loop automatically includes the property of any prototype object, consider checking the key using hasOwnProperty.

When iterating over the keys of an object, this includes not only the keys of the object, but also keys contained in the prototype of that object. It is generally a best practice to check for these keys specifically:

var someObject;
for (var key in someObject) {
    if ( ! someObject.hasOwnProperty(key)) {
        continue; // Skip keys from the prototype.
    }

    doSomethingWith(key);
}
Loading history...
156
                        if(typeof row[cell][attr] === "string"){
157
                            tCell.innerHTML = row[cell][attr];
158
                        } else if(typeof row[cell][attr] === "object"){
159
                            for(var v in row[cell][attr]){
1 ignored issue
show
Complexity introduced by
A for in loop automatically includes the property of any prototype object, consider checking the key using hasOwnProperty.

When iterating over the keys of an object, this includes not only the keys of the object, but also keys contained in the prototype of that object. It is generally a best practice to check for these keys specifically:

var someObject;
for (var key in someObject) {
    if ( ! someObject.hasOwnProperty(key)) {
        continue; // Skip keys from the prototype.
    }

    doSomethingWith(key);
}
Loading history...
160
                                tCell.setAttribute(v,row[cell][attr][v]);
161
                            }
162
                        }
163
                    }
164
                }
165
                tRow.appendChild(tCell);
166
            }
167
            tSection.appendChild(tRow);
168
            if(section === "tfoot"){
169
                this.footerProcessPaginationLinks(tSection);
170
            }
171
            this.AppendRowCalback(tableContainer);
172
        }
173
    };
174
    
175
    this.footerProcessPaginationLinks = function(tSection){
176
        var pLinks = tSection.querySelectorAll(".paging a");
177
        if(pLinks.length>0){
178
            for(var j=0; j < pLinks.length; j++){
179
                pLinks[j].setAttribute("href","javascript:void(0);");
180
                pLinks[j].setAttribute("onclick","return table.GoPage(this);");
181
            }
182
        }
183
    };
184
    
185
    this.clearSection = function(tSection){
186
        if(this.iePrior(9)){
187
            if(tSection.firstChild){
188
                while (tSection.firstChild) {
189
                    tSection.removeChild(tSection.firstChild);
190
                }  
191
            }
192
        } else {
193
            tSection.innerHTML="";
194
        }
195
    };
196
197
    this.SetTheTableColumnsHoverEffect = function (tableContainer){
198
        if(this.iePrior(9)) {return;}
199
        var tContainer = document.getElementById(tableContainer);
200
        var tHcells = tContainer.rows[0].cells;
201
        for(var i=0; i < tHcells.length; i++){
202
            if(tHcells[i].firstChild.tagName === "A"){
203
                tHcells[i].firstChild.setAttribute("onmouseover","table.ColumnHover('"+tableContainer+"',"+i+");");
204
                tHcells[i].firstChild.setAttribute("onmouseout","table.ColumnHover('"+tableContainer+"');");
205
            }
206
        }        
207
        var pLinks = tContainer.querySelectorAll("tfoot .paging a");
208
        if(pLinks.length>0){
209
            for(var j=0; j < pLinks.length; j++){
210
                pLinks[j].setAttribute("href","javascript:void(0);");
211
                pLinks[j].setAttribute("onclick","return table.GoPage(this);");
212
            }
213
        }
214
    };
215
216
    this.ColumnHover = function(tableContainer,index){
217
        if(this.iePrior(9)) {return;}
218
        var tRow = document.getElementById(tableContainer).rows;
219
        index = Math.round(index);
220
        for(var i=0; i < (tRow.length-1); i++){
221
            if(index >= 0){
222
                tRow[i].cells[index].setAttribute("lang","col-hover");
223
            } else {
224
                for(var j=0; j < tRow[i].cells.length; j++){
225
                    if(tRow[i].cells[j].lang){
226
                        tRow[i].cells[j].removeAttribute("lang");
227
                    }
228
                }
229
            }
230
        }
231
    };
232
233
    this.getFilterFieldsByTbaleID = function(tableID){
234
        var fields = {filterBy:null, filter:null};
235
        var filterDiv = this.getFilterDivByTableIDOrNull(tableID);
236
        if(filterDiv!==null) {
237
            var selectObj = filterDiv.getElementsByTagName("select")[0];
238
            var textObj = filterDiv.getElementsByTagName("input")[0];
239
            fields.filterBy = (selectObj===null || selectObj.options[selectObj.selectedIndex].value==="all") ? null : selectObj.options[selectObj.selectedIndex].value;
240
            fields.filter = (textObj===null || textObj.value.length === 0) ? null : encodeURIComponent(textObj.value.trim());
241
        }
242
        return fields;
243
    };
244
245
    this.getFilterDivByTableIDOrNull = function(tableID){
246
        var res = null;
247
        if(document.getElementById(tableID).parentNode.getElementsByTagName("div").length > 0){
248
            for (var i = 0; i < document.getElementById(tableID).parentNode.getElementsByTagName("div").length; i++) { 
249
                if(document.getElementById(tableID).parentNode.getElementsByTagName("div")[i].getAttribute("class")==="filter"){
250
                    return document.getElementById(tableID).parentNode.getElementsByTagName("div")[i];
251
                }
252
            }
253
254
        }
255
        return res;
256
    };
257
258
    this.LoadData = function(tableContainer,rq){
259
        this.setVisability(tableContainer, false);
260
        if (window.XMLHttpRequest) { xmlhttp=new XMLHttpRequest(); /* code for IE7+, Firefox, Chrome, Opera, Safari */
261
        } else {  xmlhttp=new /** global: ActiveXObject */ActiveXObject("Microsoft.XMLHTTP"); /* code for IE6, IE5 */}
0 ignored issues
show
Bug introduced by
The variable ActiveXObject seems to be never declared. If this is a global, consider adding a /** global: ActiveXObject */ comment.

This checks looks for references to variables that have not been declared. This is most likey a typographical error or a variable has been renamed.

To learn more about declaring variables in Javascript, see the MDN.

Loading history...
262
        for (var i = 0; i < this.tail.length; i++) { 
263
            var ex_xmlhttp = this.tail.shift();
264
            ex_xmlhttp.abort();
265
        }
266
        xmlhttp.onreadystatechange = function() {
267
            if (xmlhttp.readyState === 4 && xmlhttp.status === 200) {
268
                d = JSON.parse(xmlhttp.responseText);
269
                table.DrawSection(tableContainer,d.body);
270
                table.DrawSection(tableContainer,d.footer,"tfoot");
271
                table.LoadEndCalback(tableContainer);
272
                table.setVisability(tableContainer, true);
273
                if(typeof rq === "object"){
274
                    table.ColumnHover(tableContainer,rq.colNo);
275
                }
276
            }
277
        };
278
        xmlhttp.open("GET", this.RequestToUrl(rq), true);
279
        xmlhttp.send();
280
        this.tail.push(xmlhttp); //put in tail to may later abort any previous
281
    };
282
    
283
    this.setVisability = function(tableContainer,rq){
284
        var tbl = document.getElementById(tableContainer);
285
        if(rq===true){
286
            tbl.style.filter = "none";
287
            tbl.style.opacity = "1";
288
            tbl.style.cursor = "auto";
289
        } else if(rq===false){
290
            tbl.style.filter = "blur(1px)";
291
            tbl.style.opacity = "0.8";
292
            tbl.style.cursor = "wait";
293
        } else { console.log("table error in the rq value");}
0 ignored issues
show
Debugging Code introduced by
console.log looks like debug code. Are you sure you do not want to remove it?
Loading history...
294
    };
295
    
296
    this.getParent = function (obj,objType){
297
        while( obj && obj.tagName !== objType.toUpperCase() ){
298
            obj = obj.parentNode;
299
        } return obj;
300
    };
301
    
302
    this.init = function(tableId){
303
        this.SetTheTableColumnsHoverEffect(tableId);
304
    };
305
306
    this.iePrior = function(v) {var rv=false; if(/** global: navigator */navigator.appName==='Microsoft Internet Explorer') {var ua=navigator.userAgent; var re=new RegExp("MSIE ([0-9]{1,}[\.0-9]{0,})"); if(re.exec(ua)!==null) rv=parseFloat(RegExp.$1); rv=rv<v?true:false; } return rv;};
0 ignored issues
show
Bug introduced by
The variable navigator seems to be never declared. If this is a global, consider adding a /** global: navigator */ comment.

This checks looks for references to variables that have not been declared. This is most likey a typographical error or a variable has been renamed.

To learn more about declaring variables in Javascript, see the MDN.

Loading history...
Coding Style Best Practice introduced by
Curly braces around statements make for more readable code and help prevent bugs when you add further statements.

Consider adding curly braces around all statements when they are executed conditionally. This is optional if there is only one statement, but leaving them out can lead to unexpected behaviour if another statement is added later.

Consider:

if (a > 0)
    b = 42;

If you or someone else later decides to put another statement in, only the first statement will be executed.

if (a > 0)
    console.log("a > 0");
    b = 42;

In this case the statement b = 42 will always be executed, while the logging statement will be executed conditionally.

if (a > 0) {
    console.log("a > 0");
    b = 42;
}

ensures that the proper code will be executed conditionally no matter how many statements are added or removed.

Loading history...
307
    this.loadJS = function(src){ var s = document.createElement('script'); s.src = src; document.getElementsByTagName('head')[0].appendChild(s);};
308
    this.loadCSS = function(src){ var s = document.createElement('link'); s.href = src; s.rel="stylesheet"; document.getElementsByTagName('head')[0].appendChild(s);};
309
    
310
    this.LoadEndCalback = function(tableId){};
0 ignored issues
show
Unused Code introduced by
The parameter tableId is not used and could be removed.

This check looks for parameters in functions that are not used in the function body and are not followed by other parameters which are used inside the function.

Loading history...
311
    this.AppendRowCalback = function(tableId){};
0 ignored issues
show
Unused Code introduced by
The parameter tableId is not used and could be removed.

This check looks for parameters in functions that are not used in the function body and are not followed by other parameters which are used inside the function.

Loading history...
312
};
313
314
/** Moves custom created filter to the Table's filter
315
 * @param {string} filterId
316
 * @param {string} tableId
317
 * @param {boolean} delay - needed in case the table is istill not executed */
318
function moveSelectorToTheTableFilter(filterId, tableId, delay){
319
    if(delay===true){
320
        setTimeout(function(){
321
            var filterDiv = document.getElementById(tableId).getElementsByTagName("div")[0];
322
            filterDiv.appendChild(document.getElementById(filterId));
323
        },500);
324
    } else {
325
        filterDiv = document.getElementById(tableId).getElementsByTagName("div")[0];
0 ignored issues
show
Bug introduced by
The variable filterDiv seems to be never declared. Assigning variables without defining them first makes them global. If this was intended, consider making it explicit like using window.filterDiv.
Loading history...
326
        filterDiv.appendChild(document.getElementById(filterId));
327
    }
328
}
329
function changeListCustomFilter(selectObj){
330
    var fId = selectObj.options[selectObj.selectedIndex].value;
331
    var varName = selectObj.getAttribute("name");
332
    var varPos = document.URL.indexOf(varName);
333
    if(varPos>0){
334
        var url = fId!=="{!--Empty--!}" ? document.URL.substring(0,varPos) : document.URL.substring(0,(varPos-1));
335
    } else {
336
        var separator = document.URL.indexOf("?")>0 ? "&" : "?";
337
        url = document.URL + (fId!=="{!--Empty--!}" ? separator : "");
338
    }
339
    var newUrl = url + (fId!=="{!--Empty--!}" ? (varName + "=" + fId) : "");
340
    location.assign(newUrl);
341
}
342
343
344
function tablesLoadData(){
345
    var tables = document.getElementsByTagName("table");
346
    for (var i = 0; i < tables.length; i++) { 
347
        if((table.iePrior(9) ? (typeof tables[i]["data-table"]!== 'undefined') : tables[i].hasAttribute("data-table")) && tables[i].getAttribute("data-table") === "js"){
348
            table.LoadData(tables[i].id);
349
            table.SetTheTableColumnsHoverEffect(tables[i].id);
350
        }
351
    }
352
    if(table.iePrior(10)){
353
        table.loadJS("/add/helpers/table/add/json2.js");
354
    }
355
    
356
    /*if(table.iePrior(8)){ //can be used to add apropriate tables links modifications
357
        // loadCSS("/add/helpers/table/add/ie7-and-down.css");
358
    }*/
359
}
360
361
/*if(window.addEventListener){window.addEventListener('load',tablesLoadData,false);} else if(window.attachEvent){window.attachEvent('onload',tablesLoadData);}*/